package reflect;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.lang.reflect.Modifier;

/*
    属性： Field
    方法： Method
    构造方法： Constructor
    访问权限： Modifier
    研究以上五个类型的获取功能：
    1.Field getField(String name) 获取一个 public 的字段
    getDeclaredField(String name) 获取一个私有的字段

    2.Method getMethod(String name, Class<?>... args)：返回一个 Method 对象
    getDeclaredMethod(String name, Class<?>... args) 获取一个私有的方法

    3.Constructor<?> getConstructor(Class<?>... parameterTypes) 获取一个 public 的构造方法
    6.Constructor<?> getDeclaredConstructor(Class<?>... parameterTypes) 获取一个私有的构造方法
    7.int getModifiers()
 */
public class ReflectDemo2 {
    //获取类名
    public static void main4(String[] args)  throws  Exception{
        //1.获取类对象
        Class aClass = Class.forName("reflect.Student");
        System.out.println("forName方法" + aClass);
        //2.获取类对象的全类型名称
        System.out.println("getName = " + aClass.getName());
        //3.// 3. 获取aclass类对象的简单简单名称
        System.out.println("aClass.getSimpleName() = " + aClass.getSimpleName());
    }
    //获取成员方法
    public static void main3(String[] args) throws  Exception{
        //1.获取类对象
        Class clazz = Class.forName("reflect.Student");

        //2.分别获得setName方法和getName方法
        Method setName = clazz.getMethod("setName", String.class);
        Method getName = clazz.getMethod("getName");
        System.out.println("getName = " + getName);
        System.out.println("setName = " + setName);
        System.out.println("-------------------------------");
        //3.获取所有的公有的方法 clazz.getMethods()这个会把父类Object中继承过来的也获取了
        Method[] methods = clazz.getMethods();
        for (Method method : methods) {
            System.out.println("所有公开方法 " + method);
        }
        System.out.println("-------------------------------");
        //4.分别获取私有的getId和setId方法
        Method getId = clazz.getDeclaredMethod("getId");
        Method setId = clazz.getDeclaredMethod("setId", int.class);
        System.out.println("getId = " + getId);
        System.out.println("setId = " + setId);

        //5.获取所有的方法,这个不会获取Object中的方法
        Method[] declaredMethods = clazz.getDeclaredMethods();
        for (Method method : declaredMethods) {
            System.out.println("所有方法 " + method);
        }

    }
    //获取构造方法
    public static void main2(String[] args)  throws Exception {
        //1.获取类对象
        Class clazz = Class.forName("reflect.Student");
        //2.获取公开的无参构造方法
        Constructor pubCon = clazz.getConstructor();
        System.out.println("pubCon = " + pubCon);
        //3.获取公有的满参构造方法
        Constructor con = clazz.getConstructor(String.class,int.class,double.class,int.class);
        System.out.println("满参构造 " + con);

        //4.获取所有的公共构造方法
        Constructor[] constructors = clazz.getConstructors();
        for (Constructor constructor : constructors) {
            System.out.println("所有公共构造 " + constructor);
        }
        System.out.println("-------------------------------");
        //5.获取2个参数的构造方法
        Constructor con2 = clazz.getConstructor(String.class,int.class);
        System.out.println("2个参数的构造 " + con2);

        //获取私有构造方法
        Constructor con1 = clazz.getDeclaredConstructor(String.class,int.class);
        con1.setAccessible(true);
        System.out.println("私有构造 " + con1);
        System.out.println("-------------------------------");
        //6.获取所有的构造方法
        Constructor[] declaredConstructors = clazz.getDeclaredConstructors();
        for (Constructor constructor : declaredConstructors) {
            System.out.println("所有构造 " + constructor);
        }
    }

    //获取属性
    public static void main(String[] args) throws Exception {
        //1.获取类对象
        Class clazz = Class.forName("reflect.Student");
        //2.获取一个公开属性
        Field field = clazz.getField("age");
        System.out.println("pubfield = " + field);
        System.out.println("pubfield = " + Modifier.toString(field.getModifiers()));
        System.out.println("--------------------------");

        //3.获取一个私有属性
        Field name = clazz.getDeclaredField("name");
        System.out.println("name = " + name);
        System.out.println("-------------------------------");

        //4.获取所有公开属性
        Field[] fields = clazz.getFields();
        for (Field field1 : fields) {
            System.out.println("所有公开属性 " + field1);
        }
        System.out.println("-------------------------------");

        //5.获取所有属性
        Field[] declaredFields = clazz.getDeclaredFields();
        for (Field field1 : declaredFields) {
            System.out.println("所有私有属性 = " + field1);
        }
    }
}
